#include "audiostreamdecoder.h"

AudioStreamDecoder::AudioStreamDecoder(QObject *parent) :
    QThread(parent)
{
    QAudioDeviceInfo info = QAudioDeviceInfo::defaultOutputDevice();
    qDebug() << "Supported codecs:";
    foreach(QString codec, info.supportedCodecs())
    {
        qDebug() << " - " << codec;
    }
    qDebug() << "Available devices:";
    foreach(QAudioDeviceInfo deviceInfo, info.availableDevices(QAudio::AudioOutput))
    {
        qDebug() << " - " << deviceInfo.deviceName();
    }

    QAudioFormat format;
    format.setFrequency(8000);
    format.setChannels(1);
    format.setSampleSize(8);
    format.setCodec("audio/pcm");
    format.setByteOrder(QAudioFormat::LittleEndian);
    format.setSampleRate(QAudioFormat::UnSignedInt);

    if(!info.isFormatSupported(format))
    {
        qWarning() << "Default format not supported, trying nearest";
//        qDebug() << "Error: " << this->audioInput->error();
        format = info.nearestFormat(format);
    }

    qDebug() << tr("Selected format frequency: %1").arg(QString::number(format.frequency()));
    qDebug() << tr("Selected format codec: %1").arg(format.codec());
    qDebug() << tr("Selected sample size: %1").arg(QString::number(format.sampleSize()));

    this->audioOutput = new QAudioOutput(format);
    connect(this->audioOutput, SIGNAL(stateChanged(QAudio::State)), this, SLOT(outputStateChanged(QAudio::State)));
}

void AudioStreamDecoder::run()
{
    // this->audioOutput->setBufferSize(262144);
//    this->audioInput->start(this->outputFile);

    this->outputDevice = this->audioOutput->start();
//    qDebug() << this->audioInput->error();
    qDebug() << "Started";

//    this->dataDevice = this->audioInput->start();
    while(1)
    {
//        QByteArray buffer = this->outputDevice->readAll();

//        this->dataBuffer.append(buffer);

//        qDebug() << "Reading voice, got bytes: " << buffer.length() << ", bytes in buffer: " << this->dataBuffer.length();
//        if(this->dataBuffer.length() > 8192)
//        {
//            qDebug("Buffer is full, emitting signal");
//            emit chunkReady(this->dataBuffer);
//            this->dataBuffer.clear();
//        }
        if(this->playStack.length())
        {
            int periodSize = this->audioOutput->periodSize();
            qDebug() << "Got something in playing stack, playing " << periodSize << " from " << this->playStack.length();
            this->outputDevice->write(this->playStack.left(periodSize));
            this->playStack = this->playStack.remove(0, periodSize);
            this->usleep(20000);
        }
        else
        {
            this->usleep(10000);
        }
    }
}

void AudioStreamDecoder::play(QByteArray data)
{
//    this->audioOutput->setBufferSize(170);
//    qDebug() << "Period size: " << this->audioOutput->periodSize();
//    qDebug() << "Adding to play: " << data.length();
//    this->outputDevice->write(data);
//    this->outputDevice->waitForBytesWritten(10000);
    qDebug() << "Appending to playStack: " << data.length();
    this->playStack.append(data);
}

void AudioStreamDecoder::outputStateChanged(QAudio::State state)
{
    qDebug() << "Audio output state changed to " << state;
}
